/*
 * CS_EVOLUTION_POINT_GIVE_TO_ITEM.cpp
 *
 *  Created on: 2013. 6. 19.
 *      Author: mega@gamevil.com
 */

#include "../../Command.h"
#include "../../User.h"
#include "../../NLogic/Bag.h"
#include "../../NResource/Static.h"
#include "../../NUtil/Utils.h"

#include "../../GameLog.h"

namespace ProjectZ { namespace NCommand {

void SendFailEvolutionItemGivePoint(User * pUser, int res)
{
	::Network::Packet * pAck = ::Network::GETPACKETPOOL()->SEND_NEW();

	*pAck << static_cast<int16_t>(res);
	*pAck << static_cast<uint8_t>(0);
	*pAck << static_cast<uint64_t>(0);
	*pAck << static_cast<uint16_t>(0);
	*pAck << static_cast<uint8_t>(0);
	*pAck << static_cast<uint16_t>(0);
	*pAck << static_cast<uint16_t>(0);
	*pAck << static_cast<uint16_t>(0);
	*pAck << static_cast<uint16_t>(0);

	pAck->MakePacket(CMD_SC_EVOLUTION_POINT_GIVE_TO_ITEM);
	pUser->Send(pAck);
}

void Command::CS_EVOLUTION_POINT_GIVE_TO_ITEM(User * pUser, ::Network::Packet * pPacket)
{
	/*
	 * CS_EVOLUTION_POINT_GIVE_TO_ITEM                                                            0x1810
	{
			   u8                  u8bag_type;                                                                      /// 가방 타입
			   u64                 u64item_seq;                                                           /// 가방에서 몇번째 슬롯
			   u16add_point;               /// 아이템에 부여할 증가 진화포인트
	}

	SC_EVOLUTION_POINT_GIVE_TO_ITEM                                                            0x1811
	{

			   s16       s16_ack; /// 결과 값
			   u8                  u8bag_type;                                                                      /// 가방 타입
			   u64                 u64item_seq;                                                           /// 가방에서 몇번째 슬롯

			   u16                 u16evolve_point_current;                       /// 현재 보유한 진화 포인트

			   /// 변경된 아이템 진화 값들
			   u8        evolve_step;                                                                      /// 현재 진화단계
			   u16      evolve_point;                                                                     /// 진화포인트
			   u16      evolve_eff;                                                                                   /// 진화당 증가하는 증가분(%)
			   u16      evolve_eff_value;                                                       /// 진화이펙트 값(누적)
	}
	 *

	 */
	PREPARE_PACKET;
	if (false == pUser->EndBattle_afterEffect())
	{
		SendFailEvolutionItemGivePoint(pUser, ACK_BATTLE_AFTEREFFECT);
		return;
	}

	uint8_t u8bag_type		= 0;
	uint64_t u64item_seq	= 0;
	uint16_t u16add_point	= 0;

	*pPacket >> u8bag_type >> u64item_seq >> u16add_point;

	NLogic::Bag * pBag = pUser->GetBag(static_cast<INVEN_BAG_TYPE>(u8bag_type));
	if (NULL == pBag)
	{
		DEBUGLOG("CS_EVOLUTION_POINT_GIVE_TO_ITEM : pBag is NULL!! bagType=%d", u8bag_type);
		return;
	}

	NLogic::Item * pItem = pBag->GetItem(u64item_seq);
	if (NULL == pItem)
	{
		DEBUGLOG("CS_EVOLUTION_POINT_GIVE_TO_ITEM : pItem is NULL!! bagSlotIdx=%d", u64item_seq);
		return;
	}

	if (pItem->GetData().evolve_step >= pItem->GetData().evolve_max)
	{
		DEBUGLOG("CS_EVOLUTION_POINT_GIVE_TO_ITEM : Item Evolution Max!!");
		return;
	}

	// 유저의 진화 포인트 차감
	int remainPoint = pUser->GetCharacterInfo().ep_current - u16add_point;
	if (remainPoint < 0)
	{
		DEBUGLOG("CS_EVOLUTION_POINT_GIVE_TO_ITEM : remainPoint < 0");
		return;
	}

	// 아이템 진화 포인트 증감
	pItem->GetData().evolve_point += u16add_point;

	// 아이템 진화에 필요한 포인트 계산
	int needPoint = NResource::Static::Instance().GetItemEvolution()->GetEvolveNeedPoint(pItem->GetData().evolve_step);

	if (pItem->GetData().evolve_point >= needPoint)
	{
		// 기본 효과값 증가
		int newValue = NUtil::AddPercentage(pItem->GetData().eff_value[0], pItem->GetData().evolve_percent);

		// 최소한 효과값 1은 증가
		if (newValue == pItem->GetData().eff_value[0])
			pItem->GetData().eff_value[0] += 1;
		else
			pItem->GetData().eff_value[0] = newValue;

		pItem->GetData().evolve_step += 1;	// 진화 단계 갱신
		pItem->GetData().evolve_value += pItem->GetData().evolve_percent;	// 진화 효과값 누적
		pItem->GetData().evolve_point -= needPoint;	// 남은 진화 포인트 반영
	}

	if (false == pItem->UpdateDatabaseItemInfo())
	{
		DEBUGLOG("CS_EVOLUTION_POINT_GIVE_TO_ITEM : Item Update Fail!!");
		SendFailEvolutionItemGivePoint(pUser, ACK_DB_ERROR);
		return;
	}

	// 유저의 진화 포인트 갱신
	pUser->GetCharacterInfo().ep_current = remainPoint;

	int epMax = pUser->GetCharacterInfo().ep_max - u16add_point;
	pUser->GetCharacterInfo().ep_max = (epMax > 100) ? epMax : 100;

	pUser->FlushCharacterInfoCache();

	NGameLog::LogItemInfo(pUser, GIVE_POINT_EVOLUTION_ITEM, 1, 0, pItem);

	// 응답
	::Network::Packet * pAck = ::Network::GETPACKETPOOL()->SEND_NEW();

	*pAck << static_cast<int16_t>(ACK_OK);
	*pAck << u8bag_type;
	*pAck << static_cast<uint64_t>(u64item_seq);
	*pAck << static_cast<uint16_t>(pUser->GetCharacterInfo().ep_current);
	*pAck << static_cast<char>(pItem->GetData().evolve_step);
	*pAck << static_cast<uint16_t>(pItem->GetData().evolve_point);
	*pAck << static_cast<uint16_t>(pItem->GetData().evolve_percent);
	*pAck << static_cast<uint16_t>(pItem->GetData().evolve_value);
	*pAck << static_cast<uint16_t>(pItem->GetData().eff_value[0]);

	pAck->MakePacket(CMD_SC_EVOLUTION_POINT_GIVE_TO_ITEM);
	pUser->Send(pAck);
}

} /*NCommand*/ } /*ProjectZ*/

